package com.bulls.dsp.service.impl;

import com.bulls.dsp.bean.enums.AidType;
import com.bulls.dsp.bean.mybatis.Advert;
import com.bulls.dsp.bean.mybatis.Aid;
import com.bulls.dsp.bean.mybatis.AidTask;
import com.bulls.dsp.common.Constant;
import com.bulls.dsp.common.PageInfo;
import com.bulls.dsp.exception.NoSuchAdException;
import com.bulls.dsp.exception.NoSuchAidException;
import com.bulls.dsp.mapper.AdvertMapper;
import com.bulls.dsp.mapper.AidMapper;
import com.bulls.dsp.mapper.AidTaskMapper;
import com.bulls.dsp.service.IAidTaskService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import javax.annotation.Resource;
import java.util.List;
import java.util.Optional;

@Service
@Transactional
public class AidTaskServiceImpl implements IAidTaskService {

    @Resource
    private AidTaskMapper aidTaskMapper;

    @Resource
    private AdvertMapper advertMapper;

    @Resource
    private AidMapper aidMapper;

    @Override
    public void insert(AidTask aidTask) {
        this.convertName2Id(aidTask);
        aidTaskMapper.insert(aidTask);
    }

    @Override
    @Transactional(readOnly = true)
    public PageInfo<?> findAllByIfNotNull(String name, String aidType, int currentPage, int pageSize) {
        name = StringUtils.isEmpty(name) ? name : "%" + name.trim() + "%";
        aidType = StringUtils.isEmpty(aidType) ?
                aidType :
                Optional.ofNullable(AidType.getByStringValue(aidType))
                        .map(AidType::getValue)
                        .map(String::valueOf)
                        .orElse(null);

        List<AidTask> aidTasks = aidTaskMapper.getAidTasks(name, aidType, currentPage, pageSize);
        this.convertEnumsCode2Value(aidTasks);

        int total = aidTaskMapper.getAidTasksCount(name, aidType);

        return PageInfo.builder()
                .totalElements(total)
                .number(currentPage)
                .size(pageSize)
                .content(aidTasks)
                .build();
    }

    private void convertEnumsCode2Value(List<AidTask> aidTasks) {
        aidTasks.forEach(aidTask -> {
            aidTask.setAidType(
                    Optional.ofNullable(aidTask.getAidType())
                            .map(AidType::getByStringCode)
                            .map(AidType::getType)
                            .orElse(Constant.UNKNOWN)
            );
        });
    }

    private void convertName2Id(AidTask aidTask) {
        aidTask.setAdId(
                Optional.ofNullable(aidTask.getAdName())
                        .map(n -> advertMapper.getAdvertByName(n))
                        .map(Advert::getId)
                        .orElseThrow(NoSuchAdException::new)
        );

        aidTask.setAidId(
                Optional.ofNullable(aidTask.getAidName())
                        .map(n -> aidMapper.getAidByName(n))
                        .map(Aid::getId)
                        .orElseThrow(NoSuchAidException::new)
        );
    }
}
